/**
 *
 */
package com.ybkj.daijia.server.service.impl;


import com.google.gson.Gson;
import com.google.gson.reflect.TypeToken;
import com.ybkj.daijia.OrderNumberConfig;
import com.ybkj.daijia.Setting;
import com.ybkj.daijia.serverUtils.SettingUtils;
import com.ybkj.daijia.serverUtils.UseAllDataUtil;
import com.ybkj.daijia.common.PageVo;
import com.ybkj.daijia.common.Pager;
import com.ybkj.daijia.common.Principal;
import com.ybkj.daijia.common.Result;
import com.ybkj.daijia.config.ErrandApi;
import com.ybkj.daijia.config.FreightApi;
import com.ybkj.daijia.config.PassengerApi;
import com.ybkj.daijia.config.ZhuanApi;
import com.ybkj.daijia.config.ZhuanxianApi;
import com.ybkj.daijia.server.event.model.NoticeEvent;
import com.ybkj.daijia.server.mapper.CompanyMapper;
import com.ybkj.daijia.server.mapper.DriverMapper;
import com.ybkj.daijia.server.mapper.DriverPaymentsRecordMapper;
import com.ybkj.daijia.server.mapper.DriverRechargeRecordMapper;
import com.ybkj.daijia.server.mapper.FinancialRecordMapper;
import com.ybkj.daijia.server.mapper.MemberMapper;
import com.ybkj.daijia.server.mapper.NoticeMapper;
import com.ybkj.daijia.server.mapper.NoticeXDriverMapper;
import com.ybkj.daijia.server.mapper.OrderMapper;
import com.ybkj.daijia.server.mc.Passenger;
import com.ybkj.daijia.server.mc.PassengerAccount;
import com.ybkj.daijia.server.model.Company;
import com.ybkj.daijia.server.model.Driver;
import com.ybkj.daijia.server.model.DriverPaymentsRecord;
import com.ybkj.daijia.server.model.FinancialRecord;
import com.ybkj.daijia.server.model.Notice;
import com.ybkj.daijia.server.model.NoticeXDriver;
import com.ybkj.daijia.server.model.Order;
import com.ybkj.daijia.server.service.FinancialRecordService;
import java.math.BigDecimal;
import java.net.InetAddress;
import java.net.UnknownHostException;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import org.apache.commons.lang3.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.subject.Subject;
import org.json.JSONArray;
import org.json.JSONObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.event.ApplicationEventMulticaster;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

/**
 * @author Shine
 *
 */
@Service
public class DefaultFinancialRecordService implements FinancialRecordService {

    @Autowired
    private FinancialRecordMapper financialRecordMapper;

    @Autowired
    private DriverMapper driverMapper;

    @Autowired
    private MemberMapper memberMapper;

    @Autowired
    private DriverRechargeRecordMapper driverRechargeRecordMapper;

    @Autowired
    private DriverPaymentsRecordMapper driverPaymentsRecordMapper;

    @Autowired
    private SettingUtils settingUtils;

    @Autowired
    private OrderMapper orderMapper;

    @Autowired
    private CompanyMapper companyMapper;

    @Autowired
    private PassengerApi passengerApi;

    @Autowired
    private ZhuanApi zhuanApi;

    @Autowired
    private ErrandApi errandApi;

    @Autowired
    private FreightApi freightApi;

    @Autowired
    private ZhuanxianApi zhuanxianApi;

    @Autowired
    private NoticeMapper noticeMapper;

    @Autowired
    private NoticeXDriverMapper noticeXDriverMapper;

    @Autowired
    private ApplicationEventMulticaster applicationEventMulticaster;


    public PageVo<FinancialRecord> queryAll(Date start, Date end, String param, String ftype,
        Long companyId, String companyType) {

        Subject currentUser = SecurityUtils.getSubject();
        final Principal principal = (Principal) currentUser.getPrincipal();

        String likeParam = null;
        if (StringUtils.isNotBlank(param)) {
            likeParam = "%" + param + "%";
        }

        long totalElements = 0;
        List<FinancialRecord> content = new ArrayList<FinancialRecord>();

        if (!principal.isCompanyType()) {
            totalElements =
                financialRecordMapper
                    .countByCompanyWithParamAndDate(principal.getCompanyId(), likeParam,
                        ftype, start, end, companyType);
            content =
                financialRecordMapper.selectByCompanyWithParamAndDate(principal.getCompanyId(),
                    likeParam, ftype, start, end, Pager.getOffset(), Pager.getLimit(), companyType);
        } else {
            if (null != companyId) {
                totalElements =
                    financialRecordMapper
                        .countByCompanyWithParamAndDate(companyId, likeParam, ftype,
                            start, end, companyType);
                content =
                    financialRecordMapper
                        .selectByCompanyWithParamAndDate(companyId, likeParam, ftype,
                            start, end, Pager.getOffset(), Pager.getLimit(), companyType);
            } else {
                totalElements =
                    financialRecordMapper
                        .countByCompanyWithParamAndDate(null, likeParam, ftype, start,
                            end, companyType);
                content =
                    financialRecordMapper
                        .selectByCompanyWithParamAndDate(null, likeParam, ftype, start,
                            end, Pager.getOffset(), Pager.getLimit(), companyType);
            }
        }

        //获取现在服务器地址
        String host = null;
        try {
            host = InetAddress.getLocalHost().getHostAddress();
        } catch (UnknownHostException e) {

            e.printStackTrace();
        }

        //测试服务器ip
        String testHost = "172.18.0.10";
        //判断是否是测试服务器
        if (testHost.equals(host)) {
            List<FinancialRecord> newContent = new ArrayList<FinancialRecord>();
            for (FinancialRecord financialRecord : content) {
                //如果包含href字段
                if (financialRecord.getMemo().indexOf("href") != -1) {
                    String memo = financialRecord.getMemo().replace("href='", "href='/server");
                    financialRecord.setMemo(memo);
                    newContent.add(financialRecord);
                } else {
                    newContent.add(financialRecord);
                }
            }
            content = newContent;
        }

        Setting setting = settingUtils.get();

        PageVo<FinancialRecord> vo = new PageVo<FinancialRecord>();
        vo.setContent(content);
        vo.setTotalElements(totalElements);

        BigDecimal allTotal = BigDecimal.ZERO;// 所有收入
        BigDecimal thisYearTotal = BigDecimal.ZERO;// 本年收入
        BigDecimal thisMonthTotal = BigDecimal.ZERO;// 本月收入
        BigDecimal thisDayTotal = BigDecimal.ZERO;// 今日收入
        BigDecimal lastDayTotal = BigDecimal.ZERO;// 昨日收入
        BigDecimal nowMoney = BigDecimal.ZERO; // 当前搜索条件的总金额

        Calendar calendar = Calendar.getInstance();
        calendar.setTime(new Date());
        Calendar nowCalendar = Calendar.getInstance();
        int nowHour = nowCalendar.get(Calendar.HOUR_OF_DAY);
        // 今年
        calendar.set(Calendar.MONTH, 0);
        calendar.set(Calendar.DAY_OF_MONTH, 1);
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        Date thisYearStart = calendar.getTime();
        calendar.add(Calendar.YEAR, 1);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        calendar.add(Calendar.HOUR, 23);
        calendar.add(Calendar.MINUTE, 59);
        calendar.add(Calendar.SECOND, 59);
        Date thisYearEnd = calendar.getTime();
        if (setting.getWorkBegin() < nowHour) {
            calendar.add(Calendar.HOUR, -23);
            calendar.add(Calendar.MINUTE, -59);
            calendar.add(Calendar.SECOND, -59);
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.YEAR, -1);
            thisYearStart = calendar.getTime();
            calendar.add(Calendar.HOUR, 23);
            calendar.add(Calendar.MINUTE, 59);
            calendar.add(Calendar.SECOND, 59);
            calendar.add(Calendar.YEAR, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            thisYearEnd = calendar.getTime();
        }
        calendar.setTime(new Date());
        // 本月
        calendar.set(Calendar.DAY_OF_MONTH, 1);
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        Date thisMonthStart = calendar.getTime();
        calendar.add(Calendar.MONTH, 1);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        calendar.add(Calendar.HOUR, 23);
        calendar.add(Calendar.MINUTE, 59);
        calendar.add(Calendar.SECOND, 59);
        Date thisMonthEnd = calendar.getTime();
        if (setting.getWorkBegin() < nowHour) {
            calendar.add(Calendar.HOUR, -23);
            calendar.add(Calendar.MINUTE, -59);
            calendar.add(Calendar.SECOND, -59);
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.MONTH, -1);
            thisMonthStart = calendar.getTime();
            calendar.add(Calendar.MONTH, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            calendar.add(Calendar.HOUR, 23);
            calendar.add(Calendar.MINUTE, 59);
            calendar.add(Calendar.SECOND, 59);
            thisMonthEnd = calendar.getTime();
        }

        calendar.setTime(new Date());
        // 昨日
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        Date lastDayStart = calendar.getTime();
        calendar.add(Calendar.DAY_OF_MONTH, 1);
        calendar.add(Calendar.SECOND, -1);
        Date lastDayEnd = calendar.getTime();
        if (setting.getWorkBegin() > nowHour) {
            calendar.add(Calendar.SECOND, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -2);
            lastDayStart = calendar.getTime();
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.SECOND, -1);
            lastDayEnd = calendar.getTime();
        }
        // 今日
        calendar.setTime(lastDayEnd);
        calendar.add(Calendar.SECOND, 1);
        Date thisDayStart = calendar.getTime();
        calendar.setTime(thisDayStart);
        calendar.add(Calendar.DAY_OF_MONTH, 1);
        calendar.add(Calendar.SECOND, -1);
        Date thisDayEnd = calendar.getTime();
        if (principal.isCompanyType()) {
            if (null != companyId) {
                allTotal =
                    financialRecordMapper
                        .sumMoneyByCompanyWithDate(companyId, null, null, companyType);
                thisYearTotal =
                    financialRecordMapper
                        .sumMoneyByCompanyWithDate(companyId, thisYearStart, thisYearEnd,
                            companyType);
                thisMonthTotal =
                    financialRecordMapper.sumMoneyByCompanyWithDate(companyId, thisMonthStart,
                        thisMonthEnd, companyType);
                lastDayTotal =
                    financialRecordMapper
                        .sumMoneyByCompanyWithDate(companyId, lastDayStart, lastDayEnd,
                            companyType);
                thisDayTotal =
                    financialRecordMapper
                        .sumMoneyByCompanyWithDate(companyId, thisDayStart, thisDayEnd,
                            companyType);
                nowMoney =
                    financialRecordMapper
                        .sumNowMoney(companyId, likeParam, ftype, start, end, companyType);
            } else {
                allTotal = financialRecordMapper
                    .sumMoneyByCompanyWithDate(null, null, null, companyType);
                thisYearTotal =
                    financialRecordMapper
                        .sumMoneyByCompanyWithDate(null, thisYearStart, thisYearEnd,
                            companyType);
                thisMonthTotal =
                    financialRecordMapper
                        .sumMoneyByCompanyWithDate(null, thisMonthStart, thisMonthEnd,
                            companyType);
                lastDayTotal =
                    financialRecordMapper.sumMoneyByCompanyWithDate(null, lastDayStart, lastDayEnd,
                        companyType);
                thisDayTotal =
                    financialRecordMapper.sumMoneyByCompanyWithDate(null, thisDayStart, thisDayEnd,
                        companyType);
                nowMoney =
                    financialRecordMapper
                        .sumNowMoney(null, likeParam, ftype, start, end, companyType);
            }
        } else {
            allTotal =
                financialRecordMapper
                    .sumMoneyByCompanyWithDate(principal.getCompanyId(), null, null,
                        companyType);
            thisYearTotal =
                financialRecordMapper
                    .sumMoneyByCompanyWithDate(principal.getCompanyId(), thisYearStart,
                        thisYearEnd, companyType);
            thisMonthTotal =
                financialRecordMapper
                    .sumMoneyByCompanyWithDate(principal.getCompanyId(), thisMonthStart,
                        thisMonthEnd, companyType);
            lastDayTotal =
                financialRecordMapper
                    .sumMoneyByCompanyWithDate(principal.getCompanyId(), lastDayStart,
                        lastDayEnd, companyType);
            thisDayTotal =
                financialRecordMapper
                    .sumMoneyByCompanyWithDate(principal.getCompanyId(), thisDayStart,
                        thisDayEnd, companyType);
            nowMoney =
                financialRecordMapper
                    .sumNowMoney(principal.getCompanyId(), likeParam, ftype, start, end,
                        companyType);
        }

        if (null == allTotal) {
            allTotal = BigDecimal.ZERO;
        }

        if (null == thisYearTotal) {
            thisYearTotal = BigDecimal.ZERO;
        }

        if (null == thisMonthTotal) {
            thisMonthTotal = BigDecimal.ZERO;
        }

        if (null == lastDayTotal) {
            lastDayTotal = BigDecimal.ZERO;
        }
        if (null == nowMoney) {
            nowMoney = BigDecimal.ZERO;
        }
        if (null == thisDayTotal) {
            thisDayTotal = BigDecimal.ZERO;
        }
        vo.setAllTotal(allTotal);
        vo.setThisYearTotal(thisYearTotal);
        vo.setThisMonthTotal(thisMonthTotal);
        vo.setLastDayTotal(lastDayTotal);
        vo.setThisDayTotal(thisDayTotal);
        vo.setNowMoney(nowMoney);

        return vo;
    }

    @Override
    public PageVo<Driver> queryDriver(Long companyId, String param, Date start, Date end,
        Integer page, Integer limit) {
        Subject currentUser = SecurityUtils.getSubject();
        Principal principal = (Principal) currentUser.getPrincipal();

        if (!principal.isCompanyType()) {
            companyId = principal.getCompanyId();
        }

        Map<String, Object> params = new HashMap<String, Object>();
        params.put("companyId", companyId);
        if (null != page && null != limit) {
            params.put("offset", page * limit);
            params.put("size", limit);
        }

        String name = null;
        if (StringUtils.isNotBlank(param)) {
            name = "%" + param + "%";
            params.put("name", name);
        }

        List<Driver> content = driverMapper.selectByPage(params);
        long totalElements = driverMapper.countByPage(params);

        PageVo<Driver> vo = new PageVo<Driver>();
        BigDecimal total = BigDecimal.ZERO;// 所有余额
        BigDecimal allTotal = BigDecimal.ZERO;// 所有预存款
        BigDecimal imprestMoney = BigDecimal.ZERO;// 当前预存款
        BigDecimal balanceMoney = BigDecimal.ZERO;// 当前余额
        if (!CollectionUtils.isEmpty(content)) {
            for (Driver driver : content) {
                driver.setPhone(UseAllDataUtil.useAllDataDriver(driver.getPhone()));
                BigDecimal money =
                    driverPaymentsRecordMapper.sumPositiveMoneyByDriver(driver.getId(), start, end);
                if (null == money) {
                    money = BigDecimal.ZERO;
                }
                driver.setAdvance(money);
            }
        }
        vo.setContent(content);
        vo.setTotalElements(totalElements);

        allTotal = driverPaymentsRecordMapper
            .sumPositiveMoneyByCompany(companyId, null, null, null);
        total = driverMapper.sumVirtual(companyId);
        imprestMoney = driverPaymentsRecordMapper
            .sumPositiveMoneyByCompany(companyId, name, start, end);
        balanceMoney = driverMapper.sumBalanceMoney(companyId, name);

        if (null == allTotal) {
            allTotal = BigDecimal.ZERO;
        }
        if (null == total) {
            total = BigDecimal.ZERO;
        }
        if (null == imprestMoney) {
            imprestMoney = BigDecimal.ZERO;
        }
        if (null == balanceMoney) {
            balanceMoney = BigDecimal.ZERO;
        }
        vo.setAllTotal(allTotal);
        vo.setTotal(total);
        vo.setImprestMoney(imprestMoney);
        vo.setNowMoney(balanceMoney);
        return vo;
    }

    @Override
    public PageVo<Passenger> queryMember(Long companyId, String param, Integer page,
        Integer limit) {

        Subject currentUser = SecurityUtils.getSubject();
        Principal principal = (Principal) currentUser.getPrincipal();

        StringBuilder sb = new StringBuilder();
        sb.append(passengerApi.getPassengerBaseURL() + PassengerApi.QUERY_PASSENGER
            + "?appKey={appKey}&appId={appId}&sign={sign}");

        Map<String, String> kv = new HashMap<String, String>();
        if (null != page && null != limit) {
            sb.append("&page={page}");
            sb.append("&rows={rows}");

            kv.put("page", String.valueOf(Pager.getPage() + 1));
            kv.put("rows", String.valueOf(Pager.getLimit()));
        }

        if (principal.isCompanyType()) {
            if (null != companyId) {
                kv.put("companyId", String.valueOf(companyId));
                sb.append("&companyId={companyId}");
            }
        } else {
            kv.put("companyId", String.valueOf(principal.getCompanyId()));
            sb.append("&companyId={companyId}");
        }

        if (StringUtils.isNotBlank(param)) {
            kv.put("param", param);
            sb.append("&param={param}");
        }

        String result = passengerApi.get(sb.toString(), kv, settingUtils.get());

        List<Passenger> passengers = new ArrayList<Passenger>();
        long totalElements = 0;

        if (null != result) {
            JSONObject jo = new JSONObject(result);
            Integer code = jo.getInt("code");
            if (code == 0) {
                JSONObject data = jo.getJSONObject("data");
                totalElements = data.getLong("total");
                JSONArray ja = data.getJSONArray("rows");
                Gson gson = new Gson();
                passengers = gson.fromJson(ja.toString(), new TypeToken<List<Passenger>>() {
                }.getType());

            }
        }

        // Map<String, Object> params = new HashMap<String, Object>();
        // params.put("offset", Pager.getOffset());
        // params.put("size", Pager.getLimit());
        //
        // if(!principal.isCompanyType()){
        // params.put("companyId", principal.getCompanyId());
        // }
        // else{
        // if(null!=companyId){
        // params.put("companyId", companyId);
        // }
        // }
        // String name=null;
        // if(StringUtils.isNotBlank(param)){
        // name="%"+param+"%";
        // params.put("name", name);
        // }
        //
        // List<Passenger> members = memberMapper.selectByPage(params);
        // long totalElements = memberMapper.countByPage(params);

        String payType = "";
        payType += PassengerAccount.PayType.RECHARGE_TYPE_ADMIN.toString() + ",";
        payType += PassengerAccount.PayType.PAYTYPE_ADMIN.toString() + ",";
        payType += PassengerAccount.PayType.RECHARGE_TYPE_ACTIVITY.toString() + ",";
        payType += PassengerAccount.PayType.RECHARGE_TYPE_ALIPAY.toString() + ",";
        payType += PassengerAccount.PayType.RECHARGE_TYPE_WX.toString() + ",";
        payType += PassengerAccount.PayType.CASH_MODIFY.toString() + ",";
        payType += PassengerAccount.PayType.RECHARGE_TYPE_REBATE.toString() + ",";
        payType += PassengerAccount.PayType.RECHARGE_TYPE_RETURN.toString() + ",";
        payType += PassengerAccount.PayType.RECHARGE_TYPE_CANCEL_RETURN.toString();

        PageVo<Passenger> vo = new PageVo<Passenger>();
        BigDecimal total = BigDecimal.ZERO;// 所有余额
        BigDecimal allTotal = BigDecimal.ZERO;// 所有预存款
        BigDecimal imprestMoney = BigDecimal.ZERO;// 当前预存款
        BigDecimal balanceMoney = BigDecimal.ZERO;// 当前余额
        if (!CollectionUtils.isEmpty(passengers)) {
            for (Passenger passenger : passengers) {
                BigDecimal money = passengerApi
                    .sumPassengerAccountMoney(null, passenger.getId(), null, null, null, param,
                        payType, null, settingUtils.get());
                if (null == money) {
                    money = BigDecimal.ZERO;
                }
                passenger.setAdvance(money);
                passenger.setPhone(UseAllDataUtil.useAllData(passenger.getPhone()));
            }
        }
        vo.setContent(passengers);
        vo.setTotalElements(totalElements);

        if (!principal.isCompanyType()) {
            companyId = principal.getCompanyId();
        }

        allTotal = passengerApi
            .sumPassengerAccountMoney(companyId, null, null, null, null, null, payType, null,
                settingUtils.get());
        total = passengerApi.sumPassengerVirtual(companyId, null, settingUtils.get());
        imprestMoney = passengerApi
            .sumPassengerAccountMoney(companyId, null, null, null, null, param, payType, null,
                settingUtils.get());
        balanceMoney = passengerApi.sumPassengerVirtual(companyId, param, settingUtils.get());

        // allTotal = memberRechargeRecordMapper.sumAllPositiveMoneyWithCompany(companyId);
        // total =memberMapper.sumAllVirtual(companyId);
        // imprestMoney=memberRechargeRecordMapper.sumImprestMoney(companyId, name);
        // balanceMoney=memberMapper.sumBalanceMoney(companyId, name);

        // if(principal.isCompanyType()){
        // if(null!=companyId){
        // allTotal = memberRechargeRecordMapper.sumAllPositiveMoneyWithCompany(companyId);
        // total =memberMapper.sumAllVirtual(companyId);
        // imprestMoney=memberRechargeRecordMapper.sumImprestMoney(companyId, name);
        // balanceMoney=memberMapper.sumBalanceMoney(companyId, name);
        // }
        // else{
        // allTotal = memberRechargeRecordMapper.sumAllPositiveMoney();
        // total = memberMapper.sumAllVirtual(null);
        // imprestMoney=memberRechargeRecordMapper.sumImprestMoney(null, name);
        // balanceMoney=memberMapper.sumBalanceMoney(null, name);
        // }
        // }
        // else{
        // allTotal =
        // memberRechargeRecordMapper.sumAllPositiveMoneyWithCompany(principal.getCompanyId());
        // total =memberMapper.sumAllVirtual(principal.getCompanyId());
        // imprestMoney=memberRechargeRecordMapper.sumImprestMoney(principal.getCompanyId(), name);
        // balanceMoney=memberMapper.sumBalanceMoney(principal.getCompanyId(), name);
        // }

        if (null == allTotal) {
            allTotal = BigDecimal.ZERO;
        }
        vo.setAllTotal(allTotal);

        if (null == total) {
            total = BigDecimal.ZERO;
        }
        if (null == imprestMoney) {
            imprestMoney = BigDecimal.ZERO;
        }
        if (null == balanceMoney) {
            balanceMoney = BigDecimal.ZERO;
        }
        vo.setImprestMoney(imprestMoney);
        vo.setNowMoney(balanceMoney);
        vo.setTotal(total);

        return vo;
    }

    @Transactional(rollbackFor = Exception.class)
    public FinancialRecord save(FinancialRecord financialRecord) {

        financialRecordMapper.insertRecord(financialRecord);
        return financialRecord;
    }

    public FinancialRecord findOne(Long id) {

        return financialRecordMapper.selectByPrimaryKey(id);
    }

    @Transactional(rollbackFor = Exception.class)
    public int delete(FinancialRecord financialRecord) {

        int count = financialRecordMapper.deleteByPrimaryKey(financialRecord.getId());

        if (financialRecord.getType().equals(FinancialRecord.FINANCIALRECORD_TYPE_BAOXIAO)) {
            Setting setting = settingUtils.get();

            String orderNumber = "";
            Long driverId = null;
            String orderType = "";

            if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_DAIJIA)) {
                Order order = orderMapper.selectByPrimaryKey(financialRecord.getOrderId());
                orderNumber = order.getOrderNumber();
                driverId = order.getDriverId();
                orderType = "代驾";
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_ZHUANCHE)) {
                com.ybkj.daijia.server.zhuan.Order order = zhuanApi
                    .findOneOrder(financialRecord.getOrderId(), setting).getResult();
                orderNumber = order.getOrderNo();
                driverId = order.getEmployId();
                orderType = "专车";
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_PAOTUI)) {
                com.ybkj.daijia.server.errand.Order order = errandApi
                    .findOneOrder(financialRecord.getOrderId(), setting).getResult();
                orderNumber = order.getOrderNo();
                driverId = order.getEmployId();
                orderType = "跑腿";
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_FREIGHT)) {
                com.ybkj.daijia.server.freight.Order order = freightApi
                    .findOneOrder(financialRecord.getOrderId(), setting).getResult();
                orderNumber = order.getOrderNo();
                driverId = order.getEmployId();
                orderType = "货运";
            } else if (financialRecord.getOrderType()
                .equals(FinancialRecord.ORDER_TYPE_ZHUANXIAN)) {
                com.ybkj.daijia.server.zhuanxian.Order order = zhuanxianApi
                    .findOne(financialRecord.getOrderId(), setting).getResult();
                orderNumber = order.getOrderNo();
                driverId = order.getEmployId();
                orderType = "城际专线";
            }
            if (null != driverId) {
                Driver driver = driverMapper.selectByPrimaryKey(driverId);
                if (null != driver) {
                    Subject currentUser = SecurityUtils.getSubject();
                    Principal principal = (Principal) currentUser.getPrincipal();

                    Notice notice = new Notice();
                    notice.setCompanyId(principal.getCompanyId());
                    notice.setContent(
                        "您申请的" + orderType + "订单（" + orderNumber + "）报销费用（" + financialRecord
                            .getMoney().negate() + "元）已被管理员驳回");
                    notice.setOperating(principal.getUsername());
                    noticeMapper.insertRecord(notice);

                    NoticeXDriver noticeXDriver = new NoticeXDriver();
                    noticeXDriver.setDriverId(driver.getId());
                    noticeXDriver.setNoticeId(notice.getId());
                    noticeXDriver.setHasRead(false);
                    noticeXDriverMapper.insertRecord(noticeXDriver);

                    List<Driver> driverList = new ArrayList<Driver>();
                    driverList.add(driver);

                    NoticeEvent noticeEvent = new NoticeEvent(notice, driverList);
                    applicationEventMulticaster.multicastEvent(noticeEvent);
                }
            }
        }

        return count;

    }

    @Override
    public long getRunningNumber() {
        return financialRecordMapper.getRunningNumber();
    }

    @Transactional(rollbackFor = Exception.class)
    public Result<FinancialRecord> audit(FinancialRecord financialRecord) {

        Setting setting = settingUtils.get();

        Result<FinancialRecord> vo = new Result<FinancialRecord>();

        if (financialRecord.getType().equals(FinancialRecord.FINANCIALRECORD_TYPE_BAOXIAO)) {

            if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_DAIJIA)) {
                orderMapper
                    .baoxiao(financialRecord.getOrderId(), financialRecord.getMoney().negate());
                vo.setSuccess(true);
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_ZHUANCHE)) {
                Result<com.ybkj.daijia.server.zhuan.Order> result = zhuanApi
                    .baoxiao(financialRecord.getOrderId(), financialRecord.getMoney().negate(),
                        setting);
                if (result.isSuccess()) {
                    vo.setSuccess(true);
                } else {
                    vo.setMessage(result.getMessage());
                }
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_PAOTUI)) {
                Result<com.ybkj.daijia.server.errand.Order> result = errandApi
                    .baoxiao(financialRecord.getOrderId(), financialRecord.getMoney().negate(),
                        setting);
                if (result.isSuccess()) {
                    vo.setSuccess(true);
                } else {
                    vo.setMessage(result.getMessage());
                }
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_FREIGHT)) {
                Result<com.ybkj.daijia.server.freight.Order> result = freightApi
                    .baoxiao(financialRecord.getOrderId(), financialRecord.getMoney().negate(),
                        setting);
                if (result.isSuccess()) {
                    vo.setSuccess(true);
                } else {
                    vo.setMessage(result.getMessage());
                }
            } else if (financialRecord.getOrderType()
                .equals(FinancialRecord.ORDER_TYPE_ZHUANXIAN)) {
                Result<com.ybkj.daijia.server.zhuanxian.Order> result = zhuanxianApi
                    .baoxiao(financialRecord.getOrderId(), financialRecord.getMoney().negate(),
                        setting);
                if (result.isSuccess()) {
                    vo.setSuccess(true);
                } else {
                    vo.setMessage(result.getMessage());
                }
            }
        } else {
            vo.setSuccess(true);
        }

        if (!vo.isSuccess()) {
            return vo;
        }

        financialRecordMapper.updateByPrimaryKey(financialRecord);

        if (financialRecord.getType().equals(FinancialRecord.FINANCIALRECORD_TYPE_BAOXIAO)) {

            Long orderId = null;
            String orderNumber = "";
            Long driverId = null;
            Long orderCompanyId = null;
            Integer paymentsOrderType = null;
            String orderType = "";

            if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_DAIJIA)) {
                Order order = orderMapper.selectByPrimaryKey(financialRecord.getOrderId());
                orderId = order.getId();
                orderNumber = order.getOrderNumber();
                driverId = order.getDriverId();
                orderCompanyId = order.getCompanyId();
                paymentsOrderType = DriverPaymentsRecord.ORDER_TYPE_DAIJIA;
                orderType = "代驾";
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_ZHUANCHE)) {
                com.ybkj.daijia.server.zhuan.Order order = zhuanApi
                    .findOneOrder(financialRecord.getOrderId(), setting).getResult();
                orderId = order.getId();
                orderNumber = order.getOrderNo();
                driverId = order.getEmployId();
                orderCompanyId = order.getCompanyId();
                paymentsOrderType = DriverPaymentsRecord.ORDER_TYPE_ZHUANCHE;
                orderType = "专车";
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_PAOTUI)) {
                com.ybkj.daijia.server.errand.Order order = errandApi
                    .findOneOrder(financialRecord.getOrderId(), setting).getResult();
                orderId = order.getId();
                orderNumber = order.getOrderNo();
                driverId = order.getEmployId();
                orderCompanyId = order.getCompanyId();
                paymentsOrderType = DriverPaymentsRecord.ORDER_TYPE_PAOTUI;
                orderType = "跑腿";
            } else if (financialRecord.getOrderType().equals(FinancialRecord.ORDER_TYPE_FREIGHT)) {
                com.ybkj.daijia.server.freight.Order order = freightApi
                    .findOneOrder(financialRecord.getOrderId(), setting).getResult();
                orderId = order.getId();
                orderNumber = order.getOrderNo();
                driverId = order.getEmployId();
                orderCompanyId = order.getCompanyId();
                paymentsOrderType = DriverPaymentsRecord.ORDER_TYPE_FREIGHT;
                orderType = "货运";
            } else if (financialRecord.getOrderType()
                .equals(FinancialRecord.ORDER_TYPE_ZHUANXIAN)) {
                com.ybkj.daijia.server.zhuanxian.Order order = zhuanxianApi
                    .findOne(financialRecord.getOrderId(), setting).getResult();
                orderId = order.getId();
                orderNumber = order.getOrderNo();
                driverId = order.getEmployId();
                orderCompanyId = order.getCompanyId();
                paymentsOrderType = DriverPaymentsRecord.ORDER_TYPE_ZHUANXIAN;
                orderType = "城际专线";
            }
            if (null != driverId) {
                Driver driver = driverMapper.selectByPrimaryKey(driverId);
                if (null != driver) {
                    Subject currentUser = SecurityUtils.getSubject();
                    Principal principal = (Principal) currentUser.getPrincipal();
                    // 修改司机余额
                    driver.setVirtual(driver.getVirtual()
                        .add(financialRecord.getMoney().multiply(new BigDecimal(-1))));
                    driverMapper.updateVirtualByPrimaryKey(driver.getVirtual(), driver.getId());
                    // 生成充值记录

                    DriverPaymentsRecord driverPaymentsRecord = new DriverPaymentsRecord();
                    driverPaymentsRecord.setMoney(financialRecord.getMoney().negate());
                    driverPaymentsRecord.setAfterMoney(driver.getVirtual());
                    driverPaymentsRecord.setRecordType(DriverPaymentsRecord.RECHARGE_TYPE_BAOXIAO);
                    driverPaymentsRecord.setDriverId(driver.getId());
                    driverPaymentsRecord.setDriverRealName(driver.getRealname());
                    driverPaymentsRecord.setDriverUserName(driver.getUsername());
                    driverPaymentsRecord.setDriverPhone(driver.getPhone());
                    driverPaymentsRecord.setDriverCompanyId(driver.getCompanyId());
                    driverPaymentsRecord.setOrderId(orderId);
                    driverPaymentsRecord.setOrderNumber(orderNumber);
                    driverPaymentsRecord.setOrderType(paymentsOrderType);
                    driverPaymentsRecord.setOrderCompanyId(orderCompanyId);
                    driverPaymentsRecord.setMemo(financialRecord.getMemo());
                    driverPaymentsRecord.setOperating(principal.getUsername());
                    driverPaymentsRecord.setRcType(DriverPaymentsRecord.DIFFERENT_POSITIVE);
                    driverPaymentsRecord.setHappend(new Date());
                    driverPaymentsRecordMapper.insertRecord(driverPaymentsRecord);

                    Notice notice = new Notice();
                    notice.setCompanyId(principal.getCompanyId());
                    notice.setContent(
                        "您申请的" + orderType + "订单（\"" + orderNumber + "\"）报销费用（" + financialRecord
                            .getMoney().negate() + "元）已经充值到您的余额中，请查收");
                    notice.setOperating(principal.getUsername());
                    noticeMapper.insertRecord(notice);

                    NoticeXDriver noticeXDriver = new NoticeXDriver();
                    noticeXDriver.setDriverId(driver.getId());
                    noticeXDriver.setNoticeId(notice.getId());
                    noticeXDriver.setHasRead(false);
                    noticeXDriverMapper.insertRecord(noticeXDriver);

                    List<Driver> driverList = new ArrayList<Driver>();
                    driverList.add(driver);

                    NoticeEvent noticeEvent = new NoticeEvent(notice, driverList);
                    applicationEventMulticaster.multicastEvent(noticeEvent);
                }
            }
        }

        vo.setSuccess(true);
        return vo;

    }


    @Override
    public PageVo<DriverPaymentsRecord> queryDriverRecharge(Long companyId, String param,
        String type, Date start, Date end, Integer page, Integer limit) {

        Subject currentUser = SecurityUtils.getSubject();
        Principal principal = (Principal) currentUser.getPrincipal();

        Map<String, Object> params = new HashMap<String, Object>();
        if (null != page && null != limit) {
            params.put("offset", page * limit);
            params.put("size", limit);
        }

        if (!principal.isCompanyType()) {
            companyId = principal.getCompanyId();
        }
        params.put("companyId", companyId);

        if (StringUtils.isBlank(type)) {
            type = null;
        }
        params.put("recordType", type);

        String name = null;
        if (StringUtils.isNotBlank(param)) {
            name = "%" + param + "%";
            params.put("name", name);
        }

        if (null != start) {
            params.put("start", start);
        }
        if (null != end) {
            params.put("end", end);
        }

        List<DriverPaymentsRecord> content = driverPaymentsRecordMapper.selectRecharge(params);
        for (DriverPaymentsRecord driverPaymentsRecord : content) {
            driverPaymentsRecord.setDriverPhone(UseAllDataUtil.useAllDataDriver(driverPaymentsRecord
                .getDriverPhone()));
        }

        long totalElements = driverPaymentsRecordMapper.countRecharge(params);

        PageVo<DriverPaymentsRecord> vo = new PageVo<DriverPaymentsRecord>();
        vo.setContent(content);
        vo.setTotalElements(totalElements);

        Setting setting = settingUtils.get();

        BigDecimal allTotal = BigDecimal.ZERO;// 所有收入
        BigDecimal thisMonthTotal = BigDecimal.ZERO;// 本月收入
        BigDecimal thisDayTotal = BigDecimal.ZERO;// 今日收入
        BigDecimal lastDayTotal = BigDecimal.ZERO;// 昨日收入
        BigDecimal nowMoney = BigDecimal.ZERO; // 当前搜索条件的总金额
        BigDecimal thisYearTotal = BigDecimal.ZERO;// 本年收入

        Calendar calendar = Calendar.getInstance();
        calendar.setTime(new Date());
        Calendar nowCalendar = Calendar.getInstance();
        int nowHour = nowCalendar.get(Calendar.HOUR_OF_DAY);
        // 今年
        calendar.set(Calendar.MONTH, 0);
        calendar.set(Calendar.DAY_OF_MONTH, 1);
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        Date thisYearStart = calendar.getTime();
        calendar.add(Calendar.YEAR, 1);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        calendar.add(Calendar.HOUR, 23);
        calendar.add(Calendar.MINUTE, 59);
        calendar.add(Calendar.SECOND, 59);
        Date thisYearEnd = calendar.getTime();
        if (setting.getWorkBegin() < nowHour) {
            calendar.add(Calendar.HOUR, -23);
            calendar.add(Calendar.MINUTE, -59);
            calendar.add(Calendar.SECOND, -59);
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.YEAR, -1);
            thisYearStart = calendar.getTime();
            calendar.add(Calendar.HOUR, 23);
            calendar.add(Calendar.MINUTE, 59);
            calendar.add(Calendar.SECOND, 59);
            calendar.add(Calendar.YEAR, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            thisYearEnd = calendar.getTime();
        }
        calendar.setTime(new Date());
        // 本月
        calendar.set(Calendar.DAY_OF_MONTH, 1);
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        Date thisMonthStart = calendar.getTime();
        calendar.add(Calendar.MONTH, 1);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        calendar.add(Calendar.HOUR, 23);
        calendar.add(Calendar.MINUTE, 59);
        calendar.add(Calendar.SECOND, 59);
        Date thisMonthEnd = calendar.getTime();
        if (setting.getWorkBegin() < nowHour) {
            calendar.add(Calendar.HOUR, -23);
            calendar.add(Calendar.MINUTE, -59);
            calendar.add(Calendar.SECOND, -59);
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.MONTH, -1);
            thisMonthStart = calendar.getTime();
            calendar.add(Calendar.MONTH, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            calendar.add(Calendar.HOUR, 23);
            calendar.add(Calendar.MINUTE, 59);
            calendar.add(Calendar.SECOND, 59);
            thisMonthEnd = calendar.getTime();
        }

        calendar.setTime(new Date());
        // 昨日
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        Date lastDayStart = calendar.getTime();
        calendar.add(Calendar.DAY_OF_MONTH, 1);
        calendar.add(Calendar.SECOND, -1);
        Date lastDayEnd = calendar.getTime();
        if (setting.getWorkBegin() > nowHour) {
            calendar.add(Calendar.SECOND, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -2);
            lastDayStart = calendar.getTime();
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.SECOND, -1);
            lastDayEnd = calendar.getTime();
        }
        // 今日
        calendar.setTime(lastDayEnd);
        calendar.add(Calendar.SECOND, 1);
        Date thisDayStart = calendar.getTime();
        calendar.setTime(thisDayStart);
        calendar.add(Calendar.DAY_OF_MONTH, 1);
        calendar.add(Calendar.SECOND, -1);
        Date thisDayEnd = calendar.getTime();

        allTotal = driverPaymentsRecordMapper.sumRecharge(companyId, null, null, null, null);
        thisMonthTotal =
            driverPaymentsRecordMapper
                .sumRecharge(companyId, null, null, thisMonthStart, thisMonthEnd);
        thisDayTotal =
            driverPaymentsRecordMapper.sumRecharge(companyId, null, null, thisDayStart, thisDayEnd);
        lastDayTotal =
            driverPaymentsRecordMapper.sumRecharge(companyId, null, null, lastDayStart, lastDayEnd);
        thisYearTotal =
            driverPaymentsRecordMapper
                .sumRecharge(companyId, null, null, thisYearStart, thisYearEnd);
        nowMoney = driverPaymentsRecordMapper.sumRecharge(companyId, type, name, start, end);

        if (null == allTotal) {
            allTotal = BigDecimal.ZERO;
        }

        if (null == thisMonthTotal) {
            thisMonthTotal = BigDecimal.ZERO;
        }

        if (null == thisDayTotal) {
            thisDayTotal = BigDecimal.ZERO;
        }

        if (null == lastDayTotal) {
            lastDayTotal = BigDecimal.ZERO;
        }

        if (null == thisYearTotal) {
            thisYearTotal = BigDecimal.ZERO;
        }

        if (null == nowMoney) {
            nowMoney = BigDecimal.ZERO;
        }

        vo.setAllTotal(allTotal);
        vo.setThisMonthTotal(thisMonthTotal);
        vo.setThisDayTotal(thisDayTotal);
        vo.setLastDayTotal(lastDayTotal);
        vo.setThisYearTotal(thisYearTotal);
        vo.setNowMoney(nowMoney);

        return vo;
    }

    @Override
    public PageVo<PassengerAccount> queryMemberRecharge(Long companyId, String param,
        String payType,
        Date start, Date end) {

        Subject currentUser = SecurityUtils.getSubject();
        Principal principal = (Principal) currentUser.getPrincipal();

        StringBuilder sb = new StringBuilder();

        String api = PassengerApi.QUERY_COMPANY_ACCOUNT;
        sb.append(passengerApi.getPassengerBaseURL() + api
            + "?appKey={appKey}&appId={appId}&sign={sign}&page={page}&rows={rows}");

        Map<String, String> kv = new HashMap<String, String>();
        kv.put("page", String.valueOf(Pager.getPage() + 1));
        kv.put("rows", String.valueOf(Pager.getLimit()));
        if (StringUtils.isNotBlank(payType)) {
            kv.put("payType", String.valueOf(payType));
            sb.append("&payType={payType}");
        }
        if (principal.isCompanyType()) {
            if (null != companyId) {
                kv.put("companyId", String.valueOf(companyId));
                sb.append("&companyId={companyId}");
            }
        } else {
            kv.put("companyId", String.valueOf(principal.getCompanyId()));
            sb.append("&companyId={companyId}");
        }
        if (null != start) {
            kv.put("start", String.valueOf(start.getTime()));
            sb.append("&start={start}");
        }
        if (null != end) {
            kv.put("end", String.valueOf(end.getTime()));
            sb.append("&end={end}");
        }
        if (StringUtils.isNotBlank(param)) {
            kv.put("param", param);
            sb.append("&param={param}");
        }

        String result = passengerApi.get(sb.toString(), kv, settingUtils.get());

        List<PassengerAccount> passengerAccounts = new ArrayList<PassengerAccount>();
        long totalElements = 0;

        if (null != result) {
            JSONObject jo = new JSONObject(result);
            Integer code = jo.getInt("code");
            if (code == 0) {
                JSONObject data = jo.getJSONObject("data");
                totalElements = data.getLong("total");
                JSONArray ja = data.getJSONArray("rows");
                Gson gson = new Gson();
                passengerAccounts =
                    gson.fromJson(ja.toString(), new TypeToken<List<PassengerAccount>>() {
                    }.getType());
                for (PassengerAccount passengerAccount : passengerAccounts) {
                    passengerAccount.setPassenger_phone(UseAllDataUtil.useAllData(passengerAccount
                        .getPassenger_phone()));
                }
            }
        }

        // Map<String, Object> params = new HashMap<String, Object>();
        //
        // if(!principal.isCompanyType()){
        // params.put("companyId", principal.getCompanyId());
        // }
        // else{
        // if(null!=companyId){
        // params.put("companyId", companyId);
        // }
        // }
        //
        // params.put("type", type);
        // String likeName=null;
        // if(StringUtils.isNotBlank(param)){
        // likeName="%"+param+"%";
        // params.put("likeName",likeName );
        // }
        // if(null != start){
        // params.put("start", start);
        // }
        // if(null != end){
        // params.put("end", end);
        // }
        // params.put("offset", Pager.getOffset());
        // params.put("size", Pager.getLimit());

        // List<MemberPaymentsRecord> content =
        // memberPaymentsRecordMapper.selectByMemberRecharge(params);
        // long totalElements = memberPaymentsRecordMapper.countByMemberRecharge(params);

        // if(totalElements>0){
        // for (MemberPaymentsRecord memberPaymentsRecord : content) {
        // memberPaymentsRecord.setMember(memberMapper.selectByPrimaryKey(memberPaymentsRecord.getMemberId()));
        // }
        // }
        // if(totalElements>0){
        // for (MemberPaymentsRecord memberPaymentsRecord : content) {
        // memberPaymentsRecord.setPhone(memberAccountMapper.selectByMember(memberPaymentsRecord.getMemberId()).get(0).getPhone());
        // }
        // }

        PageVo<PassengerAccount> vo = new PageVo<PassengerAccount>();
        vo.setContent(passengerAccounts);
        vo.setTotalElements(totalElements);

        Setting setting = settingUtils.get();

        BigDecimal allTotal = BigDecimal.ZERO;// 所有收入
        BigDecimal thisMonthTotal = BigDecimal.ZERO;// 本月收入
        BigDecimal thisDayTotal = BigDecimal.ZERO;// 今日收入
        BigDecimal lastDayTotal = BigDecimal.ZERO;// 昨日收入
        BigDecimal nowMoney = BigDecimal.ZERO; // 当前搜索条件的总金额
        BigDecimal thisYearTotal = BigDecimal.ZERO;// 本年收入

        Calendar calendar = Calendar.getInstance();
        calendar.setTime(new Date());
        Calendar nowCalendar = Calendar.getInstance();
        int nowHour = nowCalendar.get(Calendar.HOUR_OF_DAY);
        // 今年
        calendar.set(Calendar.MONTH, 0);
        calendar.set(Calendar.DAY_OF_MONTH, 1);
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        Date thisYearStart = calendar.getTime();
        calendar.add(Calendar.YEAR, 1);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        calendar.add(Calendar.HOUR, 23);
        calendar.add(Calendar.MINUTE, 59);
        calendar.add(Calendar.SECOND, 59);
        Date thisYearEnd = calendar.getTime();
        if (setting.getWorkBegin() < nowHour) {
            calendar.add(Calendar.HOUR, -23);
            calendar.add(Calendar.MINUTE, -59);
            calendar.add(Calendar.SECOND, -59);
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.YEAR, -1);
            thisYearStart = calendar.getTime();
            calendar.add(Calendar.HOUR, 23);
            calendar.add(Calendar.MINUTE, 59);
            calendar.add(Calendar.SECOND, 59);
            calendar.add(Calendar.YEAR, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            thisYearEnd = calendar.getTime();
        }
        calendar.setTime(new Date());
        // 本月
        calendar.set(Calendar.DAY_OF_MONTH, 1);
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        Date thisMonthStart = calendar.getTime();
        calendar.add(Calendar.MONTH, 1);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        calendar.add(Calendar.HOUR, 23);
        calendar.add(Calendar.MINUTE, 59);
        calendar.add(Calendar.SECOND, 59);
        Date thisMonthEnd = calendar.getTime();
        if (setting.getWorkBegin() < nowHour) {
            calendar.add(Calendar.HOUR, -23);
            calendar.add(Calendar.MINUTE, -59);
            calendar.add(Calendar.SECOND, -59);
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.MONTH, -1);
            thisMonthStart = calendar.getTime();
            calendar.add(Calendar.MONTH, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            calendar.add(Calendar.HOUR, 23);
            calendar.add(Calendar.MINUTE, 59);
            calendar.add(Calendar.SECOND, 59);
            thisMonthEnd = calendar.getTime();
        }

        calendar.setTime(new Date());
        // 昨日
        calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
        calendar.set(Calendar.MINUTE, 0);
        calendar.set(Calendar.SECOND, 0);
        calendar.set(Calendar.MILLISECOND, 0);
        calendar.add(Calendar.DAY_OF_MONTH, -1);
        Date lastDayStart = calendar.getTime();
        calendar.add(Calendar.DAY_OF_MONTH, 1);
        calendar.add(Calendar.SECOND, -1);
        Date lastDayEnd = calendar.getTime();
        if (setting.getWorkBegin() > nowHour) {
            calendar.add(Calendar.SECOND, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -2);
            lastDayStart = calendar.getTime();
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.SECOND, -1);
            lastDayEnd = calendar.getTime();
        }
        // 今日
        calendar.setTime(lastDayEnd);
        calendar.add(Calendar.SECOND, 1);
        Date thisDayStart = calendar.getTime();
        calendar.setTime(thisDayStart);
        calendar.add(Calendar.DAY_OF_MONTH, 1);
        calendar.add(Calendar.SECOND, -1);
        Date thisDayEnd = calendar.getTime();

        if (!principal.isCompanyType()) {
            companyId = principal.getCompanyId();
        }

        allTotal =
            passengerApi
                .sumPassengerAccountMoney(companyId, null, null, null, null, null, null, null,
                    setting);
        thisMonthTotal =
            passengerApi
                .sumPassengerAccountMoney(companyId, null, null, thisMonthStart, thisMonthEnd, null,
                    null, null, setting);
        thisDayTotal =
            passengerApi
                .sumPassengerAccountMoney(companyId, null, null, thisDayStart, thisDayEnd, null,
                    null, null, setting);
        lastDayTotal =
            passengerApi
                .sumPassengerAccountMoney(companyId, null, null, lastDayStart, lastDayEnd, null,
                    null, null, setting);
        thisYearTotal =
            passengerApi
                .sumPassengerAccountMoney(companyId, null, null, thisYearStart, thisYearEnd, null,
                    null, null, setting);
        nowMoney =
            passengerApi
                .sumPassengerAccountMoney(companyId, null, null, start, end, param, payType, null,
                    setting);

        if (null == allTotal) {
            allTotal = BigDecimal.ZERO;
        }

        if (null == thisMonthTotal) {
            thisMonthTotal = BigDecimal.ZERO;
        }

        if (null == thisDayTotal) {
            thisDayTotal = BigDecimal.ZERO;
        }

        if (null == lastDayTotal) {
            lastDayTotal = BigDecimal.ZERO;
        }
        if (null == thisYearTotal) {
            thisYearTotal = BigDecimal.ZERO;
        }
        if (null == nowMoney) {
            nowMoney = BigDecimal.ZERO;
        }

        vo.setAllTotal(allTotal);
        vo.setThisMonthTotal(thisMonthTotal);
        vo.setThisDayTotal(thisDayTotal);
        vo.setLastDayTotal(lastDayTotal);
        vo.setThisYearTotal(thisYearTotal);
        vo.setNowMoney(nowMoney);

        return vo;
    }

    @Override
    public List<FinancialRecord> listByOrderType(int orderType) {

        return financialRecordMapper.selectAllByOrderType(orderType);

    }

    @Transactional(rollbackFor = Exception.class)
    public void baoxiao(Long driverCompanyId, Long orderCompanyId, Long orderId, Integer orderType,
        BigDecimal money, String orderNumber, String driverName, String memo) {

        DateFormat format = new SimpleDateFormat("yyyyMMdd");

        Company driverCompany = companyMapper.selectByPrimaryKey(driverCompanyId);
        Company orderCompany = companyMapper.selectByPrimaryKey(orderCompanyId);
        // 财务记录（司机报销）
        FinancialRecord financialRecord = new FinancialRecord();
        StringBuilder sb = new StringBuilder();
        sb.append(OrderNumberConfig.FINANCIAL_BAOXIAO);// 报销金额
        sb.append(OrderNumberConfig.FINANCIAL_WHO_DRIVER);// 对象 司机
        sb.append(format.format(new Date()));// 年月日时间
        sb.append(OrderNumberConfig.padZero(financialRecordMapper.getRunningNumber() + 1));// 流水号
        financialRecord.setCode(sb.toString());
        financialRecord.setCompanyId(driverCompany.getId());
        financialRecord.setCompanyName(driverCompany.getAbbreviation());
        financialRecord.setOrderCompanyId(orderCompany.getId());
        financialRecord.setOrderCompanyName(orderCompany.getAbbreviation());
        if (orderType.equals(FinancialRecord.ORDER_TYPE_DAIJIA)) {
            financialRecord.setMemo("订单号【<a target='_blank' href='/order/detail/" + orderId + "'>"
                + orderNumber + "</a>】,服务人员【" + driverName + "】报销：" + memo);
        } else if (orderType.equals(FinancialRecord.ORDER_TYPE_ZHUANCHE)) {
            financialRecord
                .setMemo("订单号【<a target='_blank' href='/zhuanche/detail/" + orderId + "'>"
                    + orderNumber + "</a>】,服务人员【" + driverName + "】报销：" + memo);
        } else if (orderType.equals(FinancialRecord.ORDER_TYPE_PAOTUI)) {
            financialRecord.setMemo("订单号【<a target='_blank' href='/errand/detail/" + orderId + "'>"
                + orderNumber + "</a>】,服务人员【" + driverName + "】报销：" + memo);
        } else if (orderType.equals(FinancialRecord.ORDER_TYPE_FREIGHT)) {
            financialRecord.setMemo("订单号【<a target='_blank' href='/freight/orderDetails/" + orderId
                + "'>" + orderNumber + "</a>】,服务人员【" + driverName + "】报销：" + memo);
        } else if (orderType.equals(FinancialRecord.ORDER_TYPE_ZHUANXIAN)) {
            financialRecord
                .setMemo("订单号【<a target='_blank' href='/zhuanxian/detail/" + orderId + "'>"
                    + orderNumber + "</a>】,服务人员【" + driverName + "】报销：" + memo);
        }
        financialRecord.setMoney(money.negate());
        financialRecord.setStatus(FinancialRecord.FINANCIALRECORD_WAIT);
        financialRecord.setWho(driverName);
        financialRecord.setOrderId(orderId);
        financialRecord.setOrderType(orderType);
        financialRecord.setType(FinancialRecord.FINANCIALRECORD_TYPE_BAOXIAO);
        try {
            if (financialRecordMapper.selectByCode(financialRecord.getCode()) < 1) {
                financialRecordMapper.insertRecord(financialRecord);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }

        Setting setting = settingUtils.get();

        if (orderType.equals(FinancialRecord.ORDER_TYPE_DAIJIA)) {
            orderMapper.baoxiao(orderId, BigDecimal.ZERO);
        } else if (orderType.equals(FinancialRecord.ORDER_TYPE_ZHUANCHE)) {
            zhuanApi.baoxiao(orderId, BigDecimal.ZERO, setting);
        } else if (orderType.equals(FinancialRecord.ORDER_TYPE_PAOTUI)) {
            errandApi.baoxiao(orderId, BigDecimal.ZERO, setting);
        } else if (orderType.equals(FinancialRecord.ORDER_TYPE_FREIGHT)) {
            freightApi.baoxiao(orderId, BigDecimal.ZERO, setting);
        } else if (orderType.equals(FinancialRecord.ORDER_TYPE_ZHUANXIAN)) {
            zhuanxianApi.baoxiao(orderId, BigDecimal.ZERO, setting);
        }
    }

    @Override
    public PageVo<PassengerAccount> exprotMemberRecharge(Long companyId, String param,
        String payType, Date start, Date end) {
        {

            Subject currentUser = SecurityUtils.getSubject();
            Principal principal = (Principal) currentUser.getPrincipal();

            StringBuilder sb = new StringBuilder();

            String api = PassengerApi.QUERY_COMPANY_ACCOUNT;
            sb.append(passengerApi.getPassengerBaseURL() + api
                + "?appKey={appKey}&appId={appId}&sign={sign}");

            Map<String, String> kv = new HashMap<String, String>();
            if (StringUtils.isNotBlank(payType)) {
                kv.put("payType", String.valueOf(payType));
                sb.append("&payType={payType}");
            }
            if (principal.isCompanyType()) {
                if (null != companyId) {
                    kv.put("companyId", String.valueOf(companyId));
                    sb.append("&companyId={companyId}");
                }
            } else {
                kv.put("companyId", String.valueOf(principal.getCompanyId()));
                sb.append("&companyId={companyId}");
            }
            if (null != start) {
                kv.put("start", String.valueOf(start.getTime()));
                sb.append("&start={start}");
            }
            if (null != end) {
                kv.put("end", String.valueOf(end.getTime()));
                sb.append("&end={end}");
            }
            if (StringUtils.isNotBlank(param)) {
                kv.put("param", param);
                sb.append("&param={param}");
            }

            String result = passengerApi.get(sb.toString(), kv, settingUtils.get());

            List<PassengerAccount> passengerAccounts = new ArrayList<PassengerAccount>();
            long totalElements = 0;
            if (null != result) {
                JSONObject jo = new JSONObject(result);
                Integer code = jo.getInt("code");
                if (code == 0) {
                    JSONObject data = jo.getJSONObject("data");
                    totalElements = data.getLong("total");
                    JSONArray ja = data.getJSONArray("rows");
                    Gson gson = new Gson();
                    passengerAccounts =
                        gson.fromJson(ja.toString(), new TypeToken<List<PassengerAccount>>() {
                        }.getType());
                    for (PassengerAccount passengerAccount : passengerAccounts) {
                        passengerAccount
                            .setPassenger_phone(UseAllDataUtil.useAllData(passengerAccount
                                .getPassenger_phone()));
                    }
                }
            }

            // Map<String, Object> params = new HashMap<String, Object>();
            //
            // if(!principal.isCompanyType()){
            // params.put("companyId", principal.getCompanyId());
            // }
            // else{
            // if(null!=companyId){
            // params.put("companyId", companyId);
            // }
            // }
            //
            // params.put("type", type);
            // String likeName=null;
            // if(StringUtils.isNotBlank(param)){
            // likeName="%"+param+"%";
            // params.put("likeName",likeName );
            // }
            // if(null != start){
            // params.put("start", start);
            // }
            // if(null != end){
            // params.put("end", end);
            // }
            // params.put("offset", Pager.getOffset());
            // params.put("size", Pager.getLimit());

            // List<MemberPaymentsRecord> content =
            // memberPaymentsRecordMapper.selectByMemberRecharge(params);
            // long totalElements = memberPaymentsRecordMapper.countByMemberRecharge(params);

            // if(totalElements>0){
            // for (MemberPaymentsRecord memberPaymentsRecord : content) {
            // memberPaymentsRecord.setMember(memberMapper.selectByPrimaryKey(memberPaymentsRecord.getMemberId()));
            // }
            // }
            // if(totalElements>0){
            // for (MemberPaymentsRecord memberPaymentsRecord : content) {
            // memberPaymentsRecord.setPhone(memberAccountMapper.selectByMember(memberPaymentsRecord.getMemberId()).get(0).getPhone());
            // }
            // }

            PageVo<PassengerAccount> vo = new PageVo<PassengerAccount>();
            vo.setContent(passengerAccounts);
            vo.setTotalElements(totalElements);

            Setting setting = settingUtils.get();

            BigDecimal allTotal = BigDecimal.ZERO;// 所有收入
            BigDecimal thisMonthTotal = BigDecimal.ZERO;// 本月收入
            BigDecimal thisDayTotal = BigDecimal.ZERO;// 今日收入
            BigDecimal lastDayTotal = BigDecimal.ZERO;// 昨日收入
            BigDecimal nowMoney = BigDecimal.ZERO; // 当前搜索条件的总金额
            BigDecimal thisYearTotal = BigDecimal.ZERO;// 本年收入

            Calendar calendar = Calendar.getInstance();
            calendar.setTime(new Date());
            Calendar nowCalendar = Calendar.getInstance();
            int nowHour = nowCalendar.get(Calendar.HOUR_OF_DAY);
            // 今年
            calendar.set(Calendar.MONTH, 0);
            calendar.set(Calendar.DAY_OF_MONTH, 1);
            calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
            calendar.set(Calendar.MINUTE, 0);
            calendar.set(Calendar.SECOND, 0);
            calendar.set(Calendar.MILLISECOND, 0);
            Date thisYearStart = calendar.getTime();
            calendar.add(Calendar.YEAR, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            calendar.add(Calendar.HOUR, 23);
            calendar.add(Calendar.MINUTE, 59);
            calendar.add(Calendar.SECOND, 59);
            Date thisYearEnd = calendar.getTime();
            if (setting.getWorkBegin() < nowHour) {
                calendar.add(Calendar.HOUR, -23);
                calendar.add(Calendar.MINUTE, -59);
                calendar.add(Calendar.SECOND, -59);
                calendar.add(Calendar.DAY_OF_MONTH, 1);
                calendar.add(Calendar.YEAR, -1);
                thisYearStart = calendar.getTime();
                calendar.add(Calendar.HOUR, 23);
                calendar.add(Calendar.MINUTE, 59);
                calendar.add(Calendar.SECOND, 59);
                calendar.add(Calendar.YEAR, 1);
                calendar.add(Calendar.DAY_OF_MONTH, -1);
                thisYearEnd = calendar.getTime();
            }
            calendar.setTime(new Date());
            // 本月
            calendar.set(Calendar.DAY_OF_MONTH, 1);
            calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
            calendar.set(Calendar.MINUTE, 0);
            calendar.set(Calendar.SECOND, 0);
            calendar.set(Calendar.MILLISECOND, 0);
            Date thisMonthStart = calendar.getTime();
            calendar.add(Calendar.MONTH, 1);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            calendar.add(Calendar.HOUR, 23);
            calendar.add(Calendar.MINUTE, 59);
            calendar.add(Calendar.SECOND, 59);
            Date thisMonthEnd = calendar.getTime();
            if (setting.getWorkBegin() < nowHour) {
                calendar.add(Calendar.HOUR, -23);
                calendar.add(Calendar.MINUTE, -59);
                calendar.add(Calendar.SECOND, -59);
                calendar.add(Calendar.DAY_OF_MONTH, 1);
                calendar.add(Calendar.MONTH, -1);
                thisMonthStart = calendar.getTime();
                calendar.add(Calendar.MONTH, 1);
                calendar.add(Calendar.DAY_OF_MONTH, -1);
                calendar.add(Calendar.HOUR, 23);
                calendar.add(Calendar.MINUTE, 59);
                calendar.add(Calendar.SECOND, 59);
                thisMonthEnd = calendar.getTime();
            }

            calendar.setTime(new Date());
            // 昨日
            calendar.set(Calendar.HOUR_OF_DAY, setting.getWorkBegin());
            calendar.set(Calendar.MINUTE, 0);
            calendar.set(Calendar.SECOND, 0);
            calendar.set(Calendar.MILLISECOND, 0);
            calendar.add(Calendar.DAY_OF_MONTH, -1);
            Date lastDayStart = calendar.getTime();
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.SECOND, -1);
            Date lastDayEnd = calendar.getTime();
            if (setting.getWorkBegin() > nowHour) {
                calendar.add(Calendar.SECOND, 1);
                calendar.add(Calendar.DAY_OF_MONTH, -2);
                lastDayStart = calendar.getTime();
                calendar.add(Calendar.DAY_OF_MONTH, 1);
                calendar.add(Calendar.SECOND, -1);
                lastDayEnd = calendar.getTime();
            }
            // 今日
            calendar.setTime(lastDayEnd);
            calendar.add(Calendar.SECOND, 1);
            Date thisDayStart = calendar.getTime();
            calendar.setTime(thisDayStart);
            calendar.add(Calendar.DAY_OF_MONTH, 1);
            calendar.add(Calendar.SECOND, -1);
            Date thisDayEnd = calendar.getTime();

            if (!principal.isCompanyType()) {
                companyId = principal.getCompanyId();
            }

            allTotal =
                passengerApi
                    .sumPassengerAccountMoney(companyId, null, null, null, null, null, null, null,
                        setting);
            thisMonthTotal =
                passengerApi
                    .sumPassengerAccountMoney(companyId, null, null, thisMonthStart, thisMonthEnd,
                        null,
                        null, null, setting);
            thisDayTotal =
                passengerApi
                    .sumPassengerAccountMoney(companyId, null, null, thisDayStart, thisDayEnd, null,
                        null, null, setting);
            lastDayTotal =
                passengerApi
                    .sumPassengerAccountMoney(companyId, null, null, lastDayStart, lastDayEnd, null,
                        null, null, setting);
            thisYearTotal =
                passengerApi
                    .sumPassengerAccountMoney(companyId, null, null, thisYearStart, thisYearEnd,
                        null,
                        null, null, setting);
            nowMoney =
                passengerApi
                    .sumPassengerAccountMoney(companyId, null, null, start, end, param, payType,
                        null,
                        setting);

            if (null == allTotal) {
                allTotal = BigDecimal.ZERO;
            }

            if (null == thisMonthTotal) {
                thisMonthTotal = BigDecimal.ZERO;
            }

            if (null == thisDayTotal) {
                thisDayTotal = BigDecimal.ZERO;
            }

            if (null == lastDayTotal) {
                lastDayTotal = BigDecimal.ZERO;
            }
            if (null == thisYearTotal) {
                thisYearTotal = BigDecimal.ZERO;
            }
            if (null == nowMoney) {
                nowMoney = BigDecimal.ZERO;
            }

            vo.setAllTotal(allTotal);
            vo.setThisMonthTotal(thisMonthTotal);
            vo.setThisDayTotal(thisDayTotal);
            vo.setLastDayTotal(lastDayTotal);
            vo.setThisYearTotal(thisYearTotal);
            vo.setNowMoney(nowMoney);

            return vo;
        }
    }

}
